package org.gitee.lz.xspring.redistool;

import java.util.*;

import com.tigerbrokers.bff.apihub.common.consts.CacheKeyEnum;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.MessageListener;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.listener.PatternTopic;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.springframework.data.redis.listener.Topic;
import org.springframework.data.redis.listener.adapter.MessageListenerAdapter;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;

/**
 * @ClassName: RedisMessageListenerConfig
 * @Description: RedisMessageListenerConfig
 * @Author: lizhen
 * @Date: 2024-01-05 19:30
 * @Version: 1.0
 **/
@Configuration
@Component
public class RedisMessageListenerConfig {

  @Autowired(required = false)
  List<IRedisPubSub> redisPubSubs;

  @Bean
  RedisMessageListenerContainer container(RedisConnectionFactory connectionFactory,
        Map<? extends MessageListener, Collection<? extends Topic>> listenerAdapters) {

    RedisMessageListenerContainer container = new RedisMessageListenerContainer();
    container.setConnectionFactory(connectionFactory);
    container.setMessageListeners(listenerAdapters);
    return container;
  }

  @Bean
  public Map<MessageListener, Collection<? extends Topic>> listenerAdapters(){
    if (!CollectionUtils.isEmpty(redisPubSubs)) {
      Map<MessageListener, Collection<? extends Topic>> map = new HashMap<>(redisPubSubs.size());
      for (IRedisPubSub redisPubSub : redisPubSubs) {
        final CacheKeyEnum cacheKeyEnum = redisPubSub.getCacheKeyEnum();
        // redis会利用反射调用receiveMessage方法
        final MessageListenerAdapter messageListenerAdapter = new MessageListenerAdapter(redisPubSub, "receiveMessage");
        messageListenerAdapter.afterPropertiesSet();
        map.put(messageListenerAdapter , Collections.singletonList(new PatternTopic(cacheKeyEnum.getKey())));
      }
      return map;
    }
    return Collections.emptyMap();
  }

  @Bean
  StringRedisTemplate template(RedisConnectionFactory connectionFactory) {
    return new StringRedisTemplate(connectionFactory);
  }
}
